; Kompiuteriu architektura (Assembleris)
; Darbas nr.3  Uzduotis nr.7
; Apdoroti: RET, MUL, IMUL
; ROBERTAS NEVECKA - Informatika - II kursas - 6 grupe

sseg     segment stack
         db      256 dup(?)
sseg     ends

dseg     segment
br       db     10,13,'$'
apie     db      10,13,'Programos parametrai "trecia [vykdomasis 
failas] [isvedimo failas]"',10,13,'Robertas Nevecka, MIF, informatika, II 
kursas. 6 grupe',10,13,10,13,'$'
fail1    db     'Vykdomasis failas: $';
fail2    db     'Rezultato failas: $';
msg1     db     'Iveskite sesioliktainio kodo eilute: ',10,13,'$'
f1       db     100 dup(0)
f2       db     100 dup(0)
f2st     db     'kodas.asm',0
f1id     dw     0
f2id     dw     0
f1buf    db     64 dup('$')
f1char   db     255,254 dup('$')
f1hex    db     255 dup('$')
retas    db     9,'ret ',9,'$'
mulas    db     9,'mul ',9,'$'
imulas   db     9,'imul',9,'$'
iksas    db     'x$'
axas     db     'ax$'
alas     db     'al$'
ahas     db     'ah$'
bxas     db     'bx$'
blas     db     'bl$'
bhas     db     'bh$'
cxas     db     'cx$'
clas     db     'cl$'
chas     db     'ch$'
dxas     db     'dx$'
dlas     db     'dl$'
dhas     db     'dh$'
spas     db     'sp$'
bpas     db     'bp$'
sias     db     'si$'
dias     db     'di$'
mo0000   db     '[bx + si]$'
mo0001   db     '[bx + di]$'
mo0010   db     '[bp + si]$'
mo0011   db     '[bp + di]$'
mo0100   db     '     [si]$'
mo0101   db     '     [di]$'
mo0110   db     '     [bp]$'
mo0111   db     '     [bx]$'
adr      db     't.adresas$'
plius    db     ' + $';
hexai    db	'0123456789ABCDEF'
hex_yra  db     2 dup(?),'$'
fileer1  db     10,13,'KLAIDA: failo atidaryti 
nepavyko',10,13,10,13,'$'
fileer2  db     10,13,'KLAIDA: failo sukurti nepavyko',10,13,10,13,'$'
dseg     ends

cseg     segment
         assume cs:cseg,ds:dseg,ss:sseg
;===============================================================================
main     proc    far
         push    ds
         sub     ax,ax
         push    ax
         mov     ax,dseg
         mov     ds,ax
         
         call    about
         call    param

theend:
         mov     ah,4Ch
         int     21h
         
main     endp
;===============================================================================
; PATIKRINA AR NEIVESTA "/?"
about    proc    near
         mov     ah,62h
         int     21h
         mov     es,bx

         mov     si,80h
         mov     al,es:[si]
         cmp     al,3
         jne     baik1
         
         inc     si
         mov     al,es:[si]
         cmp     al,' '
         jne     baik1
         
         inc     si
         mov     al,es:[si]
         cmp     al,'/'
         jne     baik1
         
         inc     si
         mov     al,es:[si]
         cmp     al,'?'
         jne     baik1

         mov     ah,09h
         lea     dx,apie
         int     21h
         jmp     theend

baik1:   ret
         endp
;===============================================================================
;PASIIMA PROGRAMOS PARAMETRUS
param    proc    near
         mov     ah,62h
         int     21h
         mov     es,bx
         
         mov     si,80h
         
         xor     cx,cx
         mov     al,es:[si]
         mov     cl,al
         cmp     al,0
         je      nera

         add     si,2
         sub     cx,2
         
         lea     di,f1
         mov     al,es:[si]
         jmp     next2
kitas:
         mov     al,'$'
         mov     [di],al
         lea     di,f2
         inc     si
         mov     al,es:[si]
next2:
         mov     [di],al
         inc     si
         inc     di
         mov     al,es:[si]
         cmp     al,' '
         je      kitas
         loop    next2

         dec     di
         mov     al,'$'
         mov     [di],al
         
         lea     dx,fail1
         mov     ah,9
         int     21h
         lea     dx,f1
         mov     ah,9
         int     21h
         lea     dx,br
         mov     ah,9
         int     21h
         lea     dx,fail2
         mov     ah,9
         int     21h
         lea     dx,f2
         mov     ah,9
         int     21h
         lea     dx,br
         mov     ah,9
         int     21h
         
         call    open
         jmp     baik2
nera:
         call    blank
baik2:
         ret
         endp
;===============================================================================
;ATIDARO SKAITYMO IR RASYMO BYLAS
open    proc      near
        mov       ah,3dh                          ;skaitymo bylos
        mov       al,0                            ;atidarymas
        lea       dx,f1
        int       21h
        jnc       tol1
        call      error1
tol1:
        mov       f1id,ax
;-------------------------------------------------------------------------------
        mov       ah,3ch                          ;rasymo bylos
        mov       cx,0                            ;atidarymas
        lea       dx,f2
        int       21h
        jnc       tol2
        call      error2
tol2:
        mov       f2id,ax
        call      darbas1
        mov       bx,f1id
        mov       ah,3Eh
        int       21h
        mov       bx,f2id
        mov       ah,3Eh
        int       21h
        ret
        endp
;===============================================================================
;ATIDARO STANDARTINI RASYMO BYLOS FAILA
blank   proc      near

        mov       ah,3ch                          ;rasymo bylos
        mov       cx,0                            ;atidarymas
        lea       dx,f2st
        int       21h
        jnc       tol3
        call      error2
tol3:
        mov       f2id,ax
        call      darbas2
        mov       bx,f2id
        mov       ah,3Eh
        int       21h
        ret
        endp
;===============================================================================
;DARBAS SU COM FAILU
darbas1 proc      near
a1:
        mov       bx,f1id
        mov       ah,3fh                            ;info -> f1buf
        mov       cx,64                             ;kiekinfo -> ax
        lea       dx,f1buf
        int       21h
        cmp       ax,0
        je        galas
        mov       cx,ax
        lea       si,f1buf
a2:
        mov       ah,11000011b                  ; RET
        cmp       [si],ah                       ; vidinis be steko 
islyginimo
        jne       ne1                           ; C3h
        call      jo1
        jmp       endas
ne1:
        mov       ah,11001011b                  ; RET
        cmp       [si],ah                       ; isorinis be steko 
islyginimo
        jne       ne2                           ; CBh
        call      jo1
        jmp       endas
ne2:
        mov       ah,11001011b                  ; RET
        cmp       [si],ah                       ; isorinis be steko 
islyginimo
        jne       ne3                           ; CBh
        call      jo1
        jmp       endas
ne3:
        mov       ah,11000010b                  ; RET
        cmp       [si],ah                       ; vidinis su steko 
islyginimu
        jne       ne4                           ; C2h jB vB
        call      jo2
        jmp       endas
ne4:
        mov       ah,11001010b                  ; RET
        cmp       [si],ah                       ; isorinis su steko 
islyginimu
        jne       ne5                           ; CAh jB vB
        call      jo2
        jmp       endas
ne5:
        mov       ah,[si]
        or        ah,00000001b                  ; MUL & IMUL
        cmp       ah,11110111b                  ; visi variantai
        jne       endas                         ; 1111011w mod 10x r/m 
poslinkis
        call      jo3                           ; x = 0: mul, x = 1: 
imul
        jmp       endas
endas:
        inc       si
        dec       cx
        cmp       cx,0
        ja        a2
        je        a1
galas:  ret
        endp
;===============================================================================
;DARBAS SU HEX EILUTE
darbas2 proc      near

        lea       dx,msg1
        mov       ah,09h
        int       21h

        lea       dx,f1char
        mov       ah,0Ah
        int       21h
        
        lea       si,f1char
        lea       di,f1hex
        add       si,2
c1:
        xor       ax,ax
        mov       ah,[si]
        cmp       ah,39h
        ja        ne_sk1
        sub       ah,30h
        jmp       sk1
ne_sk1: sub       ah,37h
sk1:    inc       si
        mov       al,[si]
        cmp       al,39h
        ja        ne_sk2
        sub       al,30h
        jmp       sk2
ne_sk2: sub       al,37h
sk2:    rol       ah,4
        or        ah,al
        mov       [di],ah
        inc       di
        add       si,2
        mov       ah,[si]
        cmp       ah,'$'
        jne       c1
        
        lea       si,f1hex
b1:
        mov       ah,11000011b                  ; RET
        cmp       [si],ah                       ; vidinis be steko 
islyginimo
        jne       nee1                           ; C3h
        call      jo1
        jmp       endas2
nee1:
        mov       ah,11001011b                  ; RET
        cmp       [si],ah                       ; isorinis be steko 
islyginimo
        jne       nee2                           ; CBh
        call      jo1
        jmp       endas2
nee2:
        mov       ah,11001011b                  ; RET
        cmp       [si],ah                       ; isorinis be steko 
islyginimo
        jne       nee3                           ; CBh
        call      jo1
        jmp       endas2
nee3:
        mov       ah,11000010b                  ; RET
        cmp       [si],ah                       ; vidinis su steko 
islyginimu
        jne       nee4                           ; C2h jB vB
        call      jo2
        jmp       endas2
nee4:
        mov       ah,11001010b                  ; RET
        cmp       [si],ah                       ; isorinis su steko 
islyginimu
        jne       nee5                           ; CAh jB vB
        call      jo2
        jmp       endas2
nee5:
        mov       ah,[si]
        or        ah,00000001b                  ; MUL & IMUL
        cmp       ah,11110111b                  ; visi variantai
        jne       endas2                         ; 1111011w mod 10x r/m 
poslinkis
        call      jo3                           ; x = 0: mul, x = 1: 
imul
endas2:
        inc       si
        mov       ah,[si]
        cmp       ah,0Dh
        jne       b1
galas2:
        ret
        endp
;===============================================================================
;PROCEDUROS SURADUS KOMANDAS
;-------------------------------------------------------------------------------
;RET: C3 ir CB
jo1     proc      near
        mov       bx,f2id
        push      cx
        
        lea       dx,retas
        mov       ah,9
        int       21h
        
        mov       ah,40h
        mov       cx,5
        int       21h
        
        lea       dx,br
        mov       ah,9
        int       21h
        
        mov       ah,40h
        mov       cx,2
        int       21h
        pop       cx
        ret
        endp
;-------------------------------------------------------------------------------
;RET: C2 ir CA
jo2     proc      near
        mov       bx,f2id
        push      cx
        
        lea       dx,retas
        mov       ah,9
        int       21h
        
        mov       ah,40h
        mov       cx,5
        int       21h
        
        inc       si
        mov       al,[si+1]
        call      hexas
        lea       dx,hex_yra
        mov       ah,09h
        int       21h
        mov       ah,40h
        mov       cx,2
        int       21h

        mov       al,[si]
        call      hexas
        lea       dx,hex_yra
        mov       ah,09h
        int       21h
        mov       ah,40h
        mov       cx,2
        int       21h

        lea       dx,br
        mov       ah,9
        int       21h
        
        mov       ah,40h
        mov       cx,2
        int       21h
        
        pop       cx
        ret
        endp
;===============================================================================
; MUL ir IMUL
jo3     proc      near
        push      cx

        inc       si                        ; mod 100/101 r/m:
        mov       ah,[si]                   ; nagrinejamas 100/101
        and       ah,00111000b
        cmp       ah,00101000b
        je        yra_imul
        lea       dx,mulas
        jmp       next1
yra_imul:
        lea       dx,imulas
next1:
        mov       ah,09h
        int       21h                        ; isspausdinta mul arba 
imul
        
        mov       ah,40h
        mov       cx,6
        int       21h
;------------------------------------------------------------------------------
        mov       ah,[si]                      ; nagrinejamas mod
        and       ah,11000000b                 ; jei mod = 11, tai
                                               ; operandas - registras
        cmp       ah,11000000b                 ; jei ne tai operandas 
atmintyje
        jne       perejimas1
;-------------------------------------------------------------------------------
;OPERANDAS - REGISTRAS
        mov       ah,[si-1]                    ; nagrinejamas w
        and       ah,00000001b                 ; jei w = 0 tai baitas
        cmp       ah,00000001b                 ; jei w = 1 tai zodis
        je        zod
bai:                                           ; BAITAS
        mov       ah,[si]
        and       ah,00000111b
        cmp       ah,00000000b
        je        yra_al
        cmp       ah,00000001b
        je        yra_cl
        cmp       ah,00000010b
        je        yra_dl
        cmp       ah,00000011b
        je        yra_bl
        cmp       ah,00000100b
        je        yra_ah
        cmp       ah,00000101b
        je        yra_ch
        cmp       ah,00000110b
        je        yra_dh
        cmp       ah,00000111b
        je        yra_bh
        jne       perejimas2
yra_al: lea       dx,alas
        jmp       spsd1
yra_cl: lea       dx,clas
        jmp       spsd1
yra_dl: lea       dx,dlas
        jmp       spsd1
yra_bl: lea       dx,blas
        jmp       spsd1
yra_ah: lea       dx,ahas
        jmp       spsd1
yra_ch: lea       dx,chas
        jmp       spsd1
yra_dh: lea       dx,dhas
        jmp       spsd1
yra_bh: lea       dx,bhas
spsd1:  mov       ah,09h
        int       21h
        
        mov       ah,40h
        mov       cx,2
        int       21h
        
        jmp       endas1
;-------------------------------------------------------------------------------
perejimas1:
        jmp       ne_reg                       ; perejimai, nes 
programa
perejimas2:                                    ; per didele
        jmp       endas1
;-------------------------------------------------------------------------------
zod:                                           ; ZODIS
        mov       ah,[si]
        and       ah,00000111b
        cmp       ah,00000000b
        je        yra_ax
        cmp       ah,00000001b
        je        yra_cx
        cmp       ah,00000010b
        je        yra_dx
        cmp       ah,00000011b
        je        yra_bx
        cmp       ah,00000100b
        je        yra_sp
        cmp       ah,00000101b
        je        yra_bp
        cmp       ah,00000110b
        je        yra_si
        cmp       ah,00000111b
        je        yra_di
        jne       perejimas3
yra_ax: lea       dx,axas
        jmp       spsd2
yra_cx: lea       dx,cxas
        jmp       spsd2
yra_dx: lea       dx,dxas
        jmp       spsd2
yra_bx: lea       dx,bxas
        jmp       spsd2
yra_sp: lea       dx,spas
        jmp       spsd2
yra_bp: lea       dx,bpas
        jmp       spsd2
yra_si: lea       dx,sias
        jmp       spsd2
yra_di: lea       dx,dias
spsd2:  mov       ah,09h
        int       21h
        
        mov       ah,40h
        mov       cx,2
        int       21h
        
        jmp       endas1
;-------------------------------------------------------------------------------
; OPERANDAS NE REGISTRAS, O ATMINTYJE
ne_reg:
        mov       ah,[si]
        and       ah,00000111b
        cmp       ah,00000000b
        je        m0000
        cmp       ah,00000001b
        je        m0001
        cmp       ah,00000010b
        je        m0010
        cmp       ah,00000011b
        je        m0011
        cmp       ah,00000100b
        je        m0100
        cmp       ah,00000101b
        je        m0101
        cmp       ah,00000110b
        je        m0110
        cmp       ah,00000111b
        je        m0111
        jne       perejimas4
        
perejimas3:
        jmp       endas1
        
m0000:  lea       dx,mo0000
        jmp       spsd3
m0001:  lea       dx,mo0001
        jmp       spsd3
m0010:  lea       dx,mo0010
        jmp       spsd3
m0011:  lea       dx,mo0011
        jmp       spsd3
m0100:  lea       dx,mo0100
        jmp       spsd3
m0101:  lea       dx,mo0101
        jmp       spsd3
m0110:  lea       dx,mo0110
        jmp       spsd3
m0111:  lea       dx,mo0111
spsd3:  mov       ah,09h
        int       21h
        mov       ah,40h
        mov       cx,9
        int       21h
        jmp       perejimas5

perejimas4:
        jmp       endas1
perejimas5:
        mov       ah,[si]                    ; nagrinejamas mod
        and       ah,11000000b               ; mod = 00, tai poslinkio 
nera
                                             ; mod = 01, poslinkis 
baitas
        cmp       ah,00000000b               ; mod = 10, poslinkis 
zodis
        je        endas1
        cmp       ah,01000000b
        je        mod_01
        cmp       ah,10000000b
        je        mod_10
mod_01:
        inc       si                         ; poslinkis baitas
        lea       dx,plius
        mov       ah,09h
        int       21h
        mov       ah,40h
        mov       cx,3
        int       21h
        mov       al,[si]
        call      hexas
        lea       dx,hex_yra
        mov       ah,09h
        int       21h
        mov       ah,40h
        mov       cx,2
        int       21h
        jmp       endas1
mod_10:
        inc       si                         ; poslinkis zodis
        lea       dx,plius
        mov       ah,09h
        int       21h
        mov       ah,40h
        mov       cx,3
        int       21h
        mov       al,[si]
        call      hexas
        lea       dx,hex_yra
        mov       ah,09h
        int       21h
        mov       ah,40h
        mov       cx,2
        int       21h
        inc       si
        mov       al,[si]
        call      hexas
        lea       dx,hex_yra
        mov       ah,09h
        int       21h
        mov       ah,40h
        mov       cx,2
        int       21h
        
endas1:
        lea       dx,br
        mov       ah,9
        int       21h
        
        mov       ah,40h
        mov       cx,2
        int       21h
        
        pop       cx
        ret
        endp
;===============================================================================
; PROCEDURA GRAZINANTI 16taini skaiciu
proc	hexas
        push    bx
	mov	ah,al
	and	al,0Fh
	lea	bx,[hexai]
	xlatb
	mov	[hex_yra+1],al
	shr	ax,12
	xlatb
	mov	[hex_yra],al
        pop     bx
	ret
        endp
;===============================================================================
;KLAIDA SU FAILO ATIDARYMU
error1  proc      near
        lea       dx,fileer1
        mov       ah,9
        int       21h
        jmp       theend
        ret
        endp
;===============================================================================
;KLAIDA SU FAILO SUKURIMU
error2  proc      near
        lea       dx,fileer2
        mov       ah,9
        int       21h
        jmp       theend
        ret
        endp
;===============================================================================
cseg     ends
end      main